//console.cpp

#include <cssysdef.h>
#include "console.h"
//#include "csutil/csstring.h"
#include <iutil/event.h>
#include <csutil/eventnames.h>

void ctaConsole::ExecCallback::Execute(const char *cmd)
{
	python->RunText(cmd);
}
bool ctaConsole::ExecCallback::InitPython(iObjectRegistry *obj_reg)
{
	python = csQueryRegistryOrLoad<iScript> (obj_reg,
			"crystalspace.script.python");
	if(!python)
	{
		csReport (obj_reg,
				CS_REPORTER_SEVERITY_ERROR, "cta.console",
				"Can't load the python script module!");
		return false;
	}
	python->RunText("from cspace import *");
	if(!python->LoadModule("cshelper"))
		return false;
	return true;
}

bool ctaConsole::Initialize(iObjectRegistry* obj_reg)
{
	object_reg = obj_reg;

	conout = CS_QUERY_REGISTRY(obj_reg, iConsoleOutput);
	if (!conout)
	{
		csReport (object_reg,
				CS_REPORTER_SEVERITY_ERROR, "cta.console",
				"Can't load the output console!");
		return false;
	}
	conin = csQueryRegistryOrLoad<iConsoleInput> (object_reg,
  		"crystalspace.console.input.standard");
	if (!conin)
	{
		csReport (object_reg,
				CS_REPORTER_SEVERITY_ERROR, "cta.console",
				"Can't load the input console!");
		return false;
	}

	conin->Bind (conout);
	conin->SetPrompt ("cta:");
	ExecCallback* cb = new ExecCallback ();
	conin->SetExecuteCallback(cb);
	if(!cb->InitPython(object_reg)) return false;

	cb->DecRef();
	conout->SetVisible(false);

	eventHandler.AttachNew (new EventHandler (this));
	csRef<iEventQueue> queue = CS_QUERY_REGISTRY(object_reg, iEventQueue);
	if (queue.IsValid())
	{
		csEventID events[]=
		{
				csevKeyboardEvent(object_reg),
				csevPostProcess(object_reg),
				CS_EVENTLIST_END
		};
		queue->RegisterListener(eventHandler,events);
	}
	FinalProcess = csevPostProcess(object_reg);

	return true;
}

ctaConsole::~ctaConsole()
{

}

bool ctaConsole::HandleEvent(iEvent &ev)
{

	if (CS_IS_KEYBOARD_EVENT(object_reg, ev))
	{
		csKeyEventType eventtype = csKeyEventHelper::GetEventType(&ev);
		if (eventtype == csKeyEventTypeDown)
		{
			// The user pressed a key (as opposed to releasing it
			utf32_char code = csKeyEventHelper::GetCookedCode(&ev);
			if (code == CSKEY_TAB)
			{
				Toggle();
				return true;
			}
		}
	}
	if (ev.Name == FinalProcess)
	{
		csRef<iGraphics3D> g3d=CS_QUERY_REGISTRY(object_reg,iGraphics3D);
		csRef<iGraphics2D> g2d=CS_QUERY_REGISTRY(object_reg,iGraphics2D);
		if (conout->GetVisible ())
		{
			g3d->BeginDraw (CSDRAW_2DGRAPHICS);
			conout->Draw2D (0);
			g3d->BeginDraw (CSDRAW_3DGRAPHICS);
			conout->Draw3D (0);
		}
		return false;
	}
	return conin->HandleEvent(ev);

}

void ctaConsole::Hide()
{
	visible= false;
	conout->SetVisible(false);
}

void ctaConsole::Show()
{
	visible= true;
	conout->SetVisible(true);
}

void ctaConsole::Toggle()
{
	visible=!visible;
	conout->SetVisible(visible);

}

bool ctaConsole::IsVisible()
{
	return visible;

}
